home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 2000 November: Tool Chest / Dev.CD Nov 00 TC Disk 1.toast / Sample Code / Files / PutAwayVolumes / PutAwayOneVolume.c next >
Encoding:
C/C++ Source or Header  |  2000-09-28  |  6.4 KB  |  276 lines  |  [TEXT/CWIE]

  1. /*
  2.     File:        PutAwayOneVolume.c
  3.     
  4.     Description:
  5.  
  6.     Author:        PG
  7.  
  8.     Copyright:     Copyright: © 1996-1999 by Apple Computer, Inc.
  9.                 all rights reserved.
  10.     
  11.     Disclaimer:    You may incorporate this sample code into your applications without
  12.                 restriction, though the sample code has been provided "AS IS" and the
  13.                 responsibility for its operation is 100% yours.  However, what you are
  14.                 not permitted to do is to redistribute the source as "DSC Sample Code"
  15.                 after having made changes. If you're going to re-distribute the source,
  16.                 we require that you make it clear in the source that the code was
  17.                 descended from Apple Sample Code, but that you've made changes.
  18.     
  19.     Change History (most recent first):
  20.                 6/25/99        Updated for Metrowerks Codewarror Pro 2.1(KG)
  21.                 03/21/96    Created(PG
  22.  
  23. */
  24. #define OLDROUTINELOCATIONS        0
  25. #define OLDROUTINENAMES            0
  26. #define SystemSevenOrLater        1
  27.  
  28. #ifndef __DIALOGS__
  29. #    include <Dialogs.h>
  30. #endif
  31.  
  32. #ifndef __AEREGISTRY__
  33. #    include <AERegistry.h>
  34. #endif
  35.  
  36. #ifndef __APPLEEVENTS__
  37. #    include <AppleEvents.h>
  38. #endif
  39.  
  40. #ifndef __MOREFILESEXTRAS__
  41. #    include "MoreFilesExtras.h"
  42. #endif
  43.  
  44. #ifndef __ALIASES__
  45. #    include <Aliases.h>
  46. #endif
  47.  
  48. #ifndef __FOLDERS__
  49. #    include <Folders.h>
  50. #endif
  51.  
  52. #include "PutAwayOneVolume.h"
  53.  
  54. #if GENERATINGCFM
  55.  
  56. #ifndef __TRAPS__
  57. #    include <Traps.h>
  58. #endif
  59.  
  60. pascal OSErr ReleaseFolder (short vRefNum, OSType folderType)
  61. {
  62.     const unsigned long selector = 0xB;
  63.  
  64.     enum
  65.     {
  66.         uppReleaseFolderInfo = kD0DispatchedPascalStackBased
  67.             | RESULT_SIZE (SIZE_CODE (sizeof(OSErr)))
  68.             | DISPATCHED_STACK_ROUTINE_SELECTOR_SIZE (SIZE_CODE (sizeof (selector)))
  69.             | DISPATCHED_STACK_ROUTINE_PARAMETER (1,SIZE_CODE (sizeof (vRefNum)))
  70.             | DISPATCHED_STACK_ROUTINE_PARAMETER (2,SIZE_CODE (sizeof (folderType)))
  71.     };
  72.  
  73.     return CallUniversalProc (GetToolTrapAddress (_AliasDispatch), uppReleaseFolderInfo, selector, vRefNum, folderType);
  74. }
  75.  
  76. #endif
  77.  
  78. static pascal OSErr BuildAppleEvent (short vRefNum, AppleEvent *event)
  79. {
  80.     OSErr err = noErr;
  81.  
  82.     FSSpecPtr fssP = (FSSpecPtr) NewPtr (sizeof (*fssP));
  83.     if (!(err = MemError ( )))
  84.     {
  85.         if (!(err = FSMakeFSSpec (vRefNum, fsRtDirID, nil, fssP)))
  86.         {
  87.             AliasHandle aliasH;
  88.         
  89.             if (!(err = NewAlias (nil, fssP, &aliasH)))
  90.             {
  91.                 HLockHi ((Handle) aliasH);
  92.                 if (!(err = MemError ( )))
  93.                 {
  94.                     Size size = GetHandleSize ((Handle) aliasH);
  95.                     if (!(err = MemError ( )))
  96.                     {
  97.                         if (!(err = AEPutParamPtr (event,keyDirectObject,typeAlias,*aliasH,size)))
  98.                         {
  99.                             AEDescList aeDescList;
  100.                         
  101.                             if (!(err = AECreateList (nil,0,false,&aeDescList)))
  102.                             {
  103.                                 if (!(err = AEPutPtr (&aeDescList,1,typeAlias,*aliasH,size)))
  104.                                     err = AEPutParamDesc (event,keySelection,&aeDescList);
  105.                         
  106.                                 AEDisposeDesc (&aeDescList);
  107.                             }
  108.                         }
  109.                     }
  110.                 }
  111.                 DisposeHandle ((Handle) aliasH);
  112.                 if (!err) err = MemError ( );
  113.             }
  114.         }
  115.         DisposePtr ((Ptr) fssP);
  116.         if (!err) err = MemError ( );
  117.     }
  118.  
  119.     return err;
  120. }
  121.  
  122. static pascal OSErr PutAwayOneVolumeByAppleEvent (short vRefNum, OSType finderLikeProcess)
  123. {
  124.     OSErr err = noErr;
  125.  
  126.     AEAddressDesc address;
  127.  
  128.     if (!(err = AECreateDesc (typeApplSignature, &finderLikeProcess, sizeof (finderLikeProcess), &address)))
  129.     {
  130.         AppleEvent event;
  131.  
  132.         if (!(err = AECreateAppleEvent (kAEFinderEvents,kAEPutAwaySelection,&address,kAutoGenerateReturnID,kAnyTransactionID,&event)))
  133.         {
  134.             if (!(err = BuildAppleEvent (vRefNum, &event)))
  135.             {
  136.                 AppleEvent reply;
  137.                 err = AESend (&event,&reply,kAENoReply,kAENormalPriority,kAEDefaultTimeout,nil,nil);
  138.             }
  139.  
  140.             AEDisposeDesc (&event);
  141.         }
  142.  
  143.         AEDisposeDesc (&address);
  144.     }
  145.  
  146.     return err;
  147. }
  148.  
  149. static pascal Boolean ConfirmEmptyTrash (short vRefNum, Boolean *confirmed)
  150. {
  151.     OSErr        err        = noErr;
  152.     DialogRef    dlgRef    = nil;
  153.     
  154.     *confirmed = false;
  155.  
  156.     dlgRef = GetNewDialog (128,nil,(DialogRef)-1);
  157.     if (dlgRef && !SetDialogDefaultItem (dlgRef,ok))
  158.     {
  159.         FSSpecPtr fssP = (FSSpecPtr) NewPtr (sizeof (FSSpec));
  160.  
  161.         if (!(err = MemError ( )))
  162.         {
  163.             if (!FSMakeFSSpec (vRefNum,fsRtDirID,nil,fssP))
  164.             {
  165.                 short itemHit;
  166.  
  167.                 ParamText (fssP->name,nil,nil,nil);
  168.                 ShowWindow (dlgRef);
  169.                 ModalDialog (nil,&itemHit);
  170.                 DisposeDialog (dlgRef);
  171.         
  172.                 if (itemHit == ok)
  173.                     *confirmed = true;
  174.             }
  175.  
  176.             DisposePtr ((Ptr) fssP);
  177.             if (!err) err = MemError ( );
  178.         }
  179.     }
  180.  
  181.     return err;
  182. }
  183.  
  184. static pascal OSErr CountFilesInDir (short vRefNum, long dirID, unsigned short *ioDrNmFls)
  185. {
  186.     OSErr err = noErr;
  187.  
  188.     CInfoPBPtr cipbp = (CInfoPBPtr) NewPtrClear (sizeof (CInfoPBRec));
  189.  
  190.     if (!(err = MemError ( )))
  191.     {
  192.         cipbp->dirInfo.ioVRefNum    = vRefNum;
  193.         cipbp->dirInfo.ioDrDirID    = dirID;
  194.         cipbp->dirInfo.ioFDirIndex    = -1; // ignore ioNamePtr
  195.  
  196.         if (!(err = PBGetCatInfoSync (cipbp)))
  197.             *ioDrNmFls = cipbp->dirInfo.ioDrNmFls;
  198.  
  199.         DisposePtr ((Ptr) cipbp);
  200.         if (!err) err = MemError ( );
  201.     }
  202.  
  203.     return err;
  204. }
  205.  
  206. static pascal OSErr EmptyTrash (short vRefNum)
  207. {
  208.     OSErr    err = noErr;
  209.  
  210.     short    foundVRefNum;
  211.     long    foundDirID;
  212.  
  213.     err = FindFolder (vRefNum,kTrashFolderType,false,&foundVRefNum,&foundDirID);
  214.  
  215.     if (err == fnfErr)    // if the trash ain't there,
  216.         err = noErr;    // consider it empty
  217.     else if (!err)
  218.     {
  219.         unsigned short ioDrNmFls;
  220.  
  221.         if (!(err = CountFilesInDir (foundVRefNum,foundDirID,&ioDrNmFls)))
  222.         {
  223.             if (ioDrNmFls)
  224.             {
  225.                 Boolean confirmed;
  226.         
  227.                 if (!(err = ConfirmEmptyTrash (foundVRefNum,&confirmed)))
  228.                 {
  229.                     if (!confirmed)
  230.                         err = userCanceledErr;
  231.                     else
  232.                     {
  233.                         FSSpecPtr fssP = (FSSpecPtr) NewPtr (sizeof (FSSpec));
  234.                 
  235.                         if (!(err = MemError ( )))
  236.                         {
  237.                             if (!(err = FSMakeFSSpec (foundVRefNum,foundDirID,nil,fssP)))
  238.                                 err = DeleteDirectory (fssP->vRefNum,fssP->parID,fssP->name);
  239.                                 // DeleteDirectory is from MoreFiles
  240.  
  241.                             DisposePtr ((Ptr) fssP);
  242.                             if (!err) err = MemError ( );
  243.                         }
  244.                     }
  245.                 }
  246.             }
  247.  
  248.             if (!err)
  249.                 err = ReleaseFolder (foundVRefNum,kTrashFolderType);
  250.         }
  251.     }
  252.  
  253.     return err;
  254. }
  255.  
  256. pascal OSErr PutAwayOneVolume (short vRefNum, OSType finderLikeProcess)
  257. {
  258.     //
  259.     //    Administrates task of unmounting a volume. If 'finderLikeProcess' is zero,
  260.     //    will attempt to unmount with internal code. (Internal code doesn't yet
  261.     //    work on PowerPC because there's no glue for ReleaseFolder.) If 'finderLikeProcess'
  262.     //    is non-zero, will send AppleEvent which conforms to the Finder Suite's
  263.     //    "put away" spec to that process. For volumes, "put away" means "unmount".
  264.     //
  265.  
  266.     OSErr err = noErr;
  267.  
  268.     if (finderLikeProcess)
  269.         err = PutAwayOneVolumeByAppleEvent (vRefNum,finderLikeProcess);
  270.     else if (!(err = EmptyTrash (vRefNum)))
  271.         err = UnmountAndEject (nil,vRefNum);
  272.         // UnmountAndEject is from MoreFiles
  273.  
  274.     return err;
  275. }
  276.